import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
import java.security.MessageDigest;
import java.util.Arrays;
import java.util.Base64;
import java.util.zip.Inflater;
import java.nio.charset.StandardCharsets;

/**
 * 尝试从参数派生密钥
 */
public class TryParameterDerivedKey {
    
    private static final String DATA_BASE64 = "wHBy2LDIay6WCgEybO8bw/5OxmVd4N++OJpwr/Tgjw+TA8iZ4HAy4bN8UWtwmeGz+dqU/zX6myCireq+q465rqUqpXLhma2aEPqTaNvUTv/Y71kVpkMBkgrjMnVkIi/iBV5eKsrTPfLWO8bt0mSbLM8ghswC2m2YRInkqWXHrc8Nw0JsNjwCllOUdtwe3NuIx8oQuQ2fqj1G3g3xMp6B4sWBNAo+SjTNuKnS4chvbaD3RYnGvSLyNYu+sqbKeRNofCwVn0lVrjCAGtC9d5nqhFiGw0vWksPfmCRn7vRsl7LnqcXb+Fal/hhREBsaRJdMrst3vOEeQI6pt3RGKZ3VOsliNziKbLiNnXp2zY2fin32okAFwIOczPgeQA1yAM4FCnuT9FYAMn5ecAOY7WFhJPcOqVThy0giCJrBzpIzEHXTin+BWBO1PR8wMzBqpf6us9mhBZGzu40mzVN34xXK646aMr8f2DcD9yGO20v5icEz3OUcAeayMq+YKmBoypmvQUnaGa8pjr7RfvvajY+7pu6QHqRAQ3NLY1KjIoT3PKjabb7owQ1Txw5+Ajfjen7VEeF/Dq03nPMtNOpqD3tCdWDHWir+akJcEPtPzK4Bo2K3FrLBZt2igZD6/04jtwoAojHibKqUM1Rj5h2iijH65eAU1XKTpqDPNtcP5lwa1bFNV+GvuzHM+N4gcoxiELhQeG7xiUcsZrJvadkDO2z+If9vLkXTSdMKrqozUjLRapyXpULcVL8negHnj+2vKZVdoGiDhXlm23XDFjLY91ZqX2eGfGNmpJxftl83N6q4dyXpzD2gR/chHfm0CukVlL8P8aPAfEDcAsyQETc5oVLzetGVSkGBbQl+axZu8U2Ap9CXaTi1b2VcI3he19nvgG8XEFnwP6Tbicm5PDDsiRjo2MRqfuPLWkcSHTmBlS6w8yrzAvth9x/bBLg8XLs8M/B/dKSfOa9sbptfTMmEuuhWbnqCyqnFSUt8lsFlcUbJdK02TcMbd789pANnrKTTfFeOUehu5XReHng4DfV7f6boQmJPnZfwuR8qFwp7vwme235RTloktlkQu/2QFl2LmCv+/8Za43dEdFba9Ae6I1p+50zunyIjGTE6/9RT+g/zgagzgV/qDDSM5VF6E2Ic62W/KkpfSPMHAk5Jwg0LlsSMnFXYCynZoDZ5M8s62V15VaEII3s/6wPCu4lba/BxPanRtw60EVsvrJ7B0mnG+hcW8AGVeG1ZBIhgPH887/bY+05b0MnSkhjlrys8GKSaukVbtnrLJmjePt+LdLe6tH2NTwxjbHhJR028ZWaQKvdC5BD2hRflDMBPKL68D6YJ2bitqnKKdEqYHdCMXtOXh68XUqwfkoF3phQtYHyrqF4Wsgukf3/gAlt/yF0dXFTIUzoDTc34MEAaLFENVFDt4PUnYw2SRT8i/bhi3tcavu6Hnjs=";
    
    private static final String ORGANIZATION = "qvdTr7A9k1DIU04ha4eP";
    private static final String APPID = "default";
    private static final String TIMESTAMP = "1761287286183";
    
    public static void main(String[] args) {
        try {
            System.out.println("=" + "=".repeat(99));
            System.out.println("尝试从参数派生密钥");
            System.out.println("=" + "=".repeat(99));
            
            // 获取data
            byte[] dataWithIV = Base64.getDecoder().decode(DATA_BASE64);
            byte[] dataIV = Arrays.copyOfRange(dataWithIV, 0, 16);
            byte[] dataEncrypted = Arrays.copyOfRange(dataWithIV, 16, dataWithIV.length);
            
            System.out.println("\ndata IV: " + bytesToHex(dataIV));
            System.out.println("参数信息:");
            System.out.println("  organization: " + ORGANIZATION);
            System.out.println("  appId: " + APPID);
            System.out.println("  timestamp: " + TIMESTAMP);
            
            // 尝试1: SHA-256(organization)
            System.out.println("\n" + "-".repeat(100));
            System.out.println("尝试1: SHA-256(organization)");
            byte[] key1 = sha256(ORGANIZATION.getBytes(StandardCharsets.UTF_8));
            System.out.println("密钥: " + bytesToHex(key1));
            tryDecrypt(key1, dataIV, dataEncrypted);
            
            // 尝试2: SHA-256(organization + appId)
            System.out.println("\n" + "-".repeat(100));
            System.out.println("尝试2: SHA-256(organization + appId)");
            byte[] key2 = sha256((ORGANIZATION + APPID).getBytes(StandardCharsets.UTF_8));
            System.out.println("密钥: " + bytesToHex(key2));
            tryDecrypt(key2, dataIV, dataEncrypted);
            
            // 尝试3: SHA-256(organization + appId + timestamp)
            System.out.println("\n" + "-".repeat(100));
            System.out.println("尝试3: SHA-256(organization + appId + timestamp)");
            byte[] key3 = sha256((ORGANIZATION + APPID + TIMESTAMP).getBytes(StandardCharsets.UTF_8));
            System.out.println("密钥: " + bytesToHex(key3));
            tryDecrypt(key3, dataIV, dataEncrypted);
            
            // 尝试4: SHA-256(appId + organization)
            System.out.println("\n" + "-".repeat(100));
            System.out.println("尝试4: SHA-256(appId + organization)");
            byte[] key4 = sha256((APPID + ORGANIZATION).getBytes(StandardCharsets.UTF_8));
            System.out.println("密钥: " + bytesToHex(key4));
            tryDecrypt(key4, dataIV, dataEncrypted);
            
            // 尝试5: SHA-256(timestamp)
            System.out.println("\n" + "-".repeat(100));
            System.out.println("尝试5: SHA-256(timestamp)");
            byte[] key5 = sha256(TIMESTAMP.getBytes(StandardCharsets.UTF_8));
            System.out.println("密钥: " + bytesToHex(key5));
            tryDecrypt(key5, dataIV, dataEncrypted);
            
            // 尝试6: MD5扩展到32字节
            System.out.println("\n" + "-".repeat(100));
            System.out.println("尝试6: MD5(organization) 重复");
            byte[] md5 = md5(ORGANIZATION.getBytes(StandardCharsets.UTF_8));
            byte[] key6 = new byte[32];
            System.arraycopy(md5, 0, key6, 0, 16);
            System.arraycopy(md5, 0, key6, 16, 16);
            System.out.println("密钥: " + bytesToHex(key6));
            tryDecrypt(key6, dataIV, dataEncrypted);
            
            System.out.println("\n❌ 所有尝试均失败");
            
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
    
    private static byte[] sha256(byte[] input) throws Exception {
        MessageDigest digest = MessageDigest.getInstance("SHA-256");
        return digest.digest(input);
    }
    
    private static byte[] md5(byte[] input) throws Exception {
        MessageDigest digest = MessageDigest.getInstance("MD5");
        return digest.digest(input);
    }
    
    private static void tryDecrypt(byte[] aesKey, byte[] iv, byte[] encrypted) {
        try {
            Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
            SecretKeySpec aesKeySpec = new SecretKeySpec(aesKey, "AES");
            IvParameterSpec ivSpec = new IvParameterSpec(iv);
            cipher.init(Cipher.DECRYPT_MODE, aesKeySpec, ivSpec);
            
            byte[] decrypted = cipher.doFinal(encrypted);
            
            System.out.println("✅ AES解密成功！长度: " + decrypted.length + " 字节");
            
            // 尝试zlib解压
            try {
                Inflater inflater = new Inflater(true);
                inflater.setInput(decrypted);
                
                byte[] decompressed = new byte[1024 * 100];
                int decompressedLength = inflater.inflate(decompressed);
                inflater.end();
                
                System.out.println("✅ zlib解压成功！长度: " + decompressedLength + " 字节");
                
                String json = new String(decompressed, 0, decompressedLength, StandardCharsets.UTF_8);
                System.out.println("\n🎉🎉🎉 成功！🎉🎉🎉");
                System.out.println("\n解密后的JSON数据:");
                System.out.println("=".repeat(100));
                System.out.println(json);
                System.out.println("=".repeat(100));
                
                System.exit(0); // 成功后退出
                
            } catch (Exception e) {
                System.out.println("  zlib解压失败: " + e.getMessage());
            }
            
        } catch (Exception e) {
            System.out.println("❌ AES解密失败: " + e.getMessage());
        }
    }
    
    private static String bytesToHex(byte[] bytes) {
        StringBuilder sb = new StringBuilder();
        for (byte b : bytes) {
            sb.append(String.format("%02x", b));
        }
        return sb.toString();
    }
}


